package top.rainbowecho.gateway.security.property;

import lombok.Getter;
import lombok.Setter;
import lombok.ToString;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.boot.convert.DurationUnit;
import org.springframework.stereotype.Component;
import top.rainbowecho.common.util.CommonKey;

import java.time.Duration;
import java.time.temporal.ChronoUnit;
import java.util.List;

/**
 * @author rainbow
 * @since 2019/12/25 18:30
 */
@Getter
@Setter
@ConfigurationProperties(prefix = "blog.security")
@Component
public class SecurityProperties {
    /**
     * 对此应用的OAuth2 客户端进行配置，可以添加或删除
     */
    private List<OAuth2ClientSecurityProperties> clients;

    private SecurityCaptchaProperties captcha = new SecurityCaptchaProperties();

    /**
     * 对各种认证方式进行配置
     */
    private SecurityAuthenticationProperties authentication = new SecurityAuthenticationProperties();

    /**
     * 验证码相关配置
     */
    private SecurityCodeProperties code = new SecurityCodeProperties();

    private SecurityJwtProperties jwt = new SecurityJwtProperties();

    private SecurityCorsProperties cors = new SecurityCorsProperties();

    @Getter
    @Setter
    public static class SecurityCorsProperties {
        private List<String> allowOrigin;

        private List<String> allowMethod;

        private List<String> allowHeader;

        private boolean allowCredentials = true;

        private String pathMapping = "/**";
    }

    @Getter
    @Setter
    public static class SecurityJwtProperties {
        // jwt默认签名秘钥
        private String signKey = CommonKey.JWT_SIGN_KEY;
    }

    @Getter
    @Setter
    public static class SecurityCodeProperties {
        /**
         * 验证码长度
         */
        private int length = 6;

        /**
         * 验证码有效时间，单位为秒
         */
        private Duration ttl = Duration.ofMinutes(2);

        private SecurityMailCodeProperties mail;
    }

    @Getter
    @Setter
    public static class SecurityMailCodeProperties {
        /**
         * 邮件验证码过滤器会拦截的路径，默认包含邮箱登录请求路径
         */
        private String urls;
    }

    @Getter
    @Setter
    public static class SecurityAuthenticationProperties {
        private SecurityMailAuthenticationProperties mail;

        private SecurityOpenIdAuthenticationProperties openId;

        private SocialProperties social = new SocialProperties();
    }

    @Getter
    @Setter
    public static class SecurityOpenIdAuthenticationProperties {
        /**
         * openId登录方式请求路径
         */
        private String processUrl;
    }

    @Getter
    @Setter
    public static class SecurityMailAuthenticationProperties {
        /**
         * 邮箱登录请求路径
         */
        private String processUrl;
    }

    @Getter
    @Setter
    @ToString
    public static class OAuth2ClientSecurityProperties {
        private String clientId;

        private String clientSecret;

        private String[] grantType;

        private String[] scope;

        /**
         * refresh_token有效时间，默认为2小时
         */
        @DurationUnit(ChronoUnit.SECONDS)
        private Duration refreshTokenTimeout = Duration.ofHours(2);

        /**
         * token有效时间，默认为2小时
         */
        @DurationUnit(ChronoUnit.SECONDS)
        private Duration tokenTimeout = Duration.ofHours(2);
    }

    @Getter
    @Setter
    public static class SecurityCaptchaProperties {
        private String app;

        private String secret;

        /**
         * 人机验证过滤器拦截的路径，默认包含表单登录请求路径
         */
        private String urls;
    }
}
